package com.hxexp.weixin.common.json;

import java.io.File;
import java.io.IOException;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import com.fasterxml.jackson.core.JsonGenerationException;
import com.fasterxml.jackson.core.JsonParseException;
import com.fasterxml.jackson.core.type.TypeReference;
import com.fasterxml.jackson.databind.JsonMappingException;
import com.fasterxml.jackson.databind.ObjectMapper;
import com.fasterxml.jackson.databind.PropertyNamingStrategy;

/**
 * Json工具类
 *
 * @author li.jiang
 *
 */
public final class JsonUtil {
    private static final Logger LOGGER = LoggerFactory.getLogger(JsonUtil.class);

    private JsonUtil() {
    }

    /**
     * 把Java对象序列化成json字符串
     *
     * @param obj
     *            值对象
     * @return json字符串
     */
    public static String writeObject2JsonString(final Object obj) {
        final ObjectMapper mapper = new ObjectMapper();
        String json = "";

        try {
            json = mapper.writeValueAsString(obj);
        } catch (IOException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
        }
        return json;
    }

    /**
     * 把Java对象序列化成json字符串
     *
     * @param obj
     *            值对象
     * @param strategy
     *            属性命名策略
     * @return json字符串
     */
    public static String writeObject2JsonString(final Object obj, PropertyNamingStrategy strategy) {
        final ObjectMapper mapper = new ObjectMapper();
        mapper.setPropertyNamingStrategy(strategy);
        String json = "";

        try {
            json = mapper.writeValueAsString(obj);
        } catch (IOException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
        }
        return json;
    }

    /**
     * 把Java对象序列化输出到文件
     *
     * @param resultFile
     *            json内容文件
     * @param value
     *            值对象
     */
    public static void writeObject2File(File resultFile, final Object value) {
        final ObjectMapper mapper = new ObjectMapper();
        try {
            mapper.writeValue(resultFile, value);
        } catch (JsonGenerationException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
        } catch (JsonMappingException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
        } catch (IOException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
        }
    }

    /**
     * 把Java对象序列化输出到文件
     *
     * @param resultFile
     *            json内容文件
     * @param value
     *            值对象
     */
    public static void writeObject2File(File resultFile, final Object value, PropertyNamingStrategy strategy) {
        final ObjectMapper mapper = new ObjectMapper();
        mapper.setPropertyNamingStrategy(strategy);
        try {
            mapper.writeValue(resultFile, value);
        } catch (JsonGenerationException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
        } catch (JsonMappingException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
        } catch (IOException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
        }
    }
    /**
     * 把json字符串转换成指定的对象
     *
     * @param json
     *            json字符串
     * @param valueType
     *            对象Class类型
     * @param strategy
     *            属性命名策略
     * @return 值对象
     */
    public static <T> T readJsonString2Object(final String json, final Class<T> valueType, PropertyNamingStrategy strategy) {
        final ObjectMapper mapper = new ObjectMapper();
        mapper.setPropertyNamingStrategy(strategy);
        try {
            return mapper.readValue(json, valueType);
        } catch (JsonParseException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (JsonMappingException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (IOException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        }
    }

    /**
     * 把json字符串转换成指定的对象
     *
     * @param json
     *            json字符串
     * @param valueType
     *            对象Class类型
     * @return 值对象
     */
    public static <T> T readJsonString2Object(final String json, final Class<T> valueType) {
        final ObjectMapper mapper = new ObjectMapper();
        try {
            return mapper.readValue(json, valueType);
        } catch (JsonParseException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (JsonMappingException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (IOException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        }
    }

    /**
     * 把json字符串转换成指定的对象
     *
     * @param json
     *            json字符串
     * @param valueTypeRef
     *            对象类型参数
     * @return 值对象
     */
    public static <T> T readJsonString2Object(final String json, final TypeReference<T> valueTypeRef) {
        final ObjectMapper mapper = new ObjectMapper();
        try {
            return mapper.readValue(json, valueTypeRef);
        } catch (JsonParseException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (JsonMappingException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (IOException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        }
    }

    /**
     * 把json字符串转换成指定的对象
     *
     * @param json
     *            json字符串
     * @param valueTypeRef
     *            对象类型参数
     * @param strategy
     *            属性命名策略
     * @return 值对象
     */
    public static <T> T readJsonString2Object(final String json, final TypeReference<T> valueTypeRef, PropertyNamingStrategy strategy) {
        final ObjectMapper mapper = new ObjectMapper();
        mapper.setPropertyNamingStrategy(strategy);
        try {
            return mapper.readValue(json, valueTypeRef);
        } catch (JsonParseException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (JsonMappingException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (IOException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        }
    }

    /**
     * 把json数据文件转换成指定类型对象
     *
     * @param jsonFile
     *            json数据文件
     * @param valueTypeRef
     *            对象类型参数
     * @return 值对象
     */
    public static <T> T readJsonFile2Object(final File jsonFile, final TypeReference<T> valueTypeRef) {
        final ObjectMapper mapper = new ObjectMapper();
        try {
            return mapper.readValue(jsonFile, valueTypeRef);
        } catch (JsonParseException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (JsonMappingException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (IOException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        }
    }

    /**
     * 把json数据文件转换成指定类型对象
     *
     * @param jsonFile
     *            json数据文件
     * @param valueTypeRef
     *            对象类型参数
     * @param strategy
     *            属性命名策略
     * @return 值对象
     */
    public static <T> T readJsonFile2Object(final File jsonFile, final TypeReference<T> valueTypeRef, PropertyNamingStrategy strategy) {
        final ObjectMapper mapper = new ObjectMapper();
        mapper.setPropertyNamingStrategy(strategy);
        try {
            return mapper.readValue(jsonFile, valueTypeRef);
        } catch (JsonParseException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (JsonMappingException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        } catch (IOException e) {
            LOGGER.error(e.getLocalizedMessage(), e);
            return null;
        }
    }
}
